package com.yugao.fintech.antelope.codegen.controller;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.yugao.fintech.antelope.codegen.core.DBConnect;
import com.yugao.fintech.antelope.codegen.core.DbType;
import com.yugao.fintech.antelope.codegen.core.GeneratorConfig;
import com.yugao.fintech.antelope.codegen.core.TableDefinition;
import com.yugao.fintech.antelope.codegen.model.entity.DatasourceConfig;
import com.yugao.fintech.antelope.codegen.model.rqrs.DatasourceConfigQuery;
import com.yugao.fintech.antelope.codegen.model.rqrs.DatasourceRS;
import com.yugao.fintech.antelope.codegen.model.rqrs.DbTableRQ;
import com.yugao.fintech.antelope.codegen.service.DatasourceConfigService;
import com.yugao.fintech.antelope.base.ram.ActionType;
import com.yugao.fintech.antelope.base.ram.RamResource;
import com.yugao.fintech.framework.core.response.Resp;
import io.swagger.annotations.Api;
import lombok.AllArgsConstructor;
import lombok.Getter;
import lombok.RequiredArgsConstructor;
import lombok.Setter;
import org.springframework.validation.annotation.Validated;

import java.util.List;
import java.util.stream.Collectors;
import java.util.stream.Stream;
@Api(tags = "低代码-数据源")
@RestController
@RequestMapping("/genDataSource")
@RequiredArgsConstructor
public class DatasourceConfigController {
    private final DatasourceConfigService datasourceConfigService;

    @PostMapping("/saveDataSource")
    @RamResource(action = "lcp:dataSource:save", name = "低代码-保存数据源", type = ActionType.WRITE)
    public Resp<?> saveDataSource(@RequestBody DatasourceConfig datasourceConfig) {
        datasourceConfigService.save(datasourceConfig);
        return Resp.ok();
    }

    @GetMapping("/listAllDataSource")
    @RamResource(action = "lcp:dataSource:query", name = "低代码-查询数据源", type = ActionType.READ)
    public Resp<List<DatasourceRS>> listAllDataSource() {
        List<DatasourceRS> datasourceConfigList = datasourceConfigService.listAll();
        return Resp.ok(datasourceConfigList);
    }

    @GetMapping("/getDataSource")
    @RamResource(action = "lcp:dataSource:query", name = "低代码-查询数据源", type = ActionType.READ)
    public Resp<DatasourceConfig> getDataSource(@RequestParam("id") Long id) {
        DatasourceConfig datasourceConfig = datasourceConfigService.getById(id);
        return Resp.ok(datasourceConfig);
    }

    @GetMapping("/pageDataSource")
    @RamResource(action = "lcp:dataSource:query", name = "低代码-查询数据源", type = ActionType.READ)
    public Resp<IPage<DatasourceConfig>> pageDataSource(DatasourceConfigQuery rq) {
        IPage<DatasourceConfig> datasourceConfigList = datasourceConfigService.page(rq);
        return Resp.ok(datasourceConfigList);
    }

    @PostMapping("/updateDataSource")
    @RamResource(action = "lcp:dataSource:update", name = "低代码-更新数据源", type = ActionType.WRITE)
    public Resp<?> updateDataSource(@RequestBody DatasourceConfig datasourceConfig) {
        datasourceConfigService.update(datasourceConfig);
        return Resp.ok();
    }

    @DeleteMapping("/deleteDataSource")
    @RamResource(action = "lcp:dataSource:delete", name = "低代码-删除数据源", type = ActionType.WRITE)
    public Resp<?> deleteDataSource(@RequestBody DatasourceConfig datasourceConfig) {
        datasourceConfigService.delete(datasourceConfig);
        return Resp.ok();
    }

    @DeleteMapping("/batchDeleteDataSource")
    @RamResource(action = "lcp:dataSource:delete", name = "低代码-删除数据源", type = ActionType.WRITE)
    public Resp<?> batchDeleteDataSource(@RequestParam("ids") List<Long> ids) {
        datasourceConfigService.deleteBatchByIds(ids);
        return Resp.ok();
    }

    @GetMapping("/listTable")
    @RamResource(action = "lcp:dataSource:delete", name = "低代码-查询数据库表", type = ActionType.READ)
    public Resp<?> listTable(@Validated DbTableRQ rq) {
        List<TableDefinition> list = datasourceConfigService.listTable(rq);
        return Resp.ok(list);
    }

    @PostMapping("/testConnection")
    @RamResource(action = "lcp:dataSource:testConnection", name = "低代码-测试数据库连接", type = ActionType.READ)
    public Resp<?> testConnection(@RequestBody DatasourceConfig datasourceConfig) {
        String error = DBConnect.testConnection(GeneratorConfig.build(datasourceConfig));
        if (error != null) {
            return Resp.fail(error);
        }
        return Resp.ok();
    }

    @PostMapping("/dbtype")
    public Resp<List<DbTypeShow>> dbType(@RequestBody DatasourceConfig datasourceConfig) {
        List<DbTypeShow> dbTypeShowList = Stream.of(DbType.values())
                .map(dbType -> new DbTypeShow(dbType.getDisplayName(), dbType.getType()))
                .collect(Collectors.toList());
        return Resp.ok(dbTypeShowList);
    }

    @Getter
    @Setter
    @AllArgsConstructor
    private static class DbTypeShow {
        private String label;
        private Integer dbType;
    }
}
